
const verify = require('./app/passport/verify');

// module.exports = app => {
//   // 初始化Table
//   app.beforeStart(async () => {
//todo app.model.sync数据同步  如果表已经存在,使用`force:true`将删除该表
//     await app.model.sync();
//   });
// };

/**
 * todo 框架提供了这些 生命周期函数供开发人员处理：
 配置文件即将加载， 这是最后动态修改配置的时机（ configWillLoad ）
 配置文件加载完成（ configDidLoad ）
 文件加载完成（ didLoad ）
 插件启动完毕（ willReady ）
 worker 准备就绪（ didReady ）
 应用启动完成（ serverDidReady ）
 应用即将关闭（ beforeClose ）
 我们可以在 app.js 中定义这个 Boot 类， 下面我们抽取几个在应用开发中常用的生命周期函数
 来举例：*/
class AppBootHook {
  constructor(app) {
    this.app = app;
  }

  configWillLoad() {
    //此时 config 文件已经被读取并合并，但是还并未生效
    // 这是应用层修改配置的最后时机
    // 注意：此函数只支持同步调用

    // 例如：参数中的密码是加密的，在此处进行解密
    // this.app.config.mysql.password = decrypt(this.app.config.mysql.password);
    // 例如：插入一个中间件到框架的 coreMiddleware 之间
    // const statusIdx = this.app.config.coreMiddleware.indexOf('status');
    // this.app.config.coreMiddleware.splice(statusIdx + 1, 0, 'limit');
    console.log('configWillLoad');
  }

  async didLoad() {
    // 所有的配置已经加载完毕
    // 可以用来加载应用自定义的文件，启动自定义的服务

    // 例如：创建自定义应用的示例
    // this.app.queue = new Queue(this.app.config.queue);
    // await this.app.queue.init();

    // 例如：加载自定义的目录
    // this.app.loader.loadToContext(path.join(__dirname, 'app/tasks'), 'tasks', {
    //   fieldClass: 'tasksClasses'
    // });
    console.log('didLoad');
  }

  async willReady() {
    // 所有的插件都已启动完毕，但是应用整体还未 ready
    // 可以做一些数据初始化等操作，这些操作成功才会启动应用

    // 例如：从数据库加载数据到内存缓存
    // this.app.cacheData = await this.app.model.query(QUERY_CACHE_SQL);
    console.log('willReady');
    //fixme ???在干啥？？？
    await this.app.model.sync({ alter: true });
    //todo passport鉴权
    this.app.passport.verify(verify);
  }

  async didReady() {
    //todo 应用已经启动完毕
    //todo 添加启动对admin的自动检查 hezhongfeng 2019/11/1 0001 15:45
    /**
     * 除了在请求时可以获取 Context 实例之外， 在有些非用户请求的场景下我们需要访问 service /
     model 等 Context 实例上的对象， todo 我们可以通过 Application.createAnonymousContext()
     方法创建一个匿名 Context 实例：*/
     const ctx = await this.app.createAnonymousContext();
    //todo 调用 ctx.service.startup.start() 方法
    await ctx.service.startup.start();
  }

  async serverDidReady() {
    // http / https server 已启动，开始接受外部请求
    // 此时可以从 app.server 拿到 server 的实例
    // this.app.server.on('timeout', socket => {
    //   // handle socket timeout
    // });
  }
}

module.exports = AppBootHook;
